package cn.iwit.util;

import java.io.UnsupportedEncodingException;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

/**
 * http相关帮助类
 * @author shujq
 * 2013-10-26 14:54
 */

public class HttpUtil {
	private static Logger logger = LoggerFactory.getLogger(HttpUtil.class);
	private static final String HTTP_JSFUND_CLIENTIP = "HTTP_JSFUND_CLIENTIP";
	private static Map<String,Object> cache = new ConcurrentHashMap<String, Object>();
	/**
	 * 获取httprequest对象
	 * @return
	 * @throws BusiException
	 */
	public static HttpServletRequest getRequest() throws BusiException {
		HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes())
				.getRequest();
		if (request == null)
			throw new BusiException(BusiException.ERR_SESSIONLOST, "request对象不存在");
		return request;
	}

	/**
	 * 获取cookie对象
	 * @param request httprequest对象，如果送空，从springmvc的上下文获取
	 * @param key
	 * @return
	 * @throws BusiException
	 */
	public static String getCookieAttribute(String key) throws BusiException {
		Cookie[] cookies = getRequest().getCookies();
		if (cookies == null || cookies.length == 0)
			return null;
		Cookie cookie;
		for (int i = 0; i < cookies.length; i++) {
			cookie = cookies[i];
			if (cookie.getName().equals(key)) {
				return cookie.getValue();
			}
		}
		return null;
	}

	/**
	 * 设置cookie值
	 * @param response
	 * @param key
	 * @param value
	 * @param maxAge cookie生存期
	 */
	public static void setCookieAttribute(HttpServletResponse response, String key, String value, int maxAge) {
		try {

			Cookie cookie = new Cookie(key, value);
			if (maxAge > 0)
				cookie.setMaxAge(maxAge);
			cookie.setPath("/");
			response.addCookie(cookie);
		} catch (Exception ex) {
			System.out.println("写cookie错误" + ex.getMessage());
		}
	}

	/**
	 * 设置cookie值，默认生存期为20天
	 * @param response
	 * @param key
	 * @param value
	 */
	public static void setCookieAttribute(HttpServletResponse response, String key, String value) {
		setCookieAttribute(response, key, value, 1728000);
	}

	/**
	 * 获取session中的值
	 * @param key
	 * @return
	 * @throws BusiException
	 */
	public static Object getAttribute(String key) throws BusiException {
		/*Object obj = getRequest().getSession().getAttribute(key);
		if (logger.isDebugEnabled())
			logger.debug("get session[{}]=[{}]", key, obj);*/
		Object obj =cache.get(key);
		return obj;
	}

	/**
	 * 设置session值
	 * @param key
	 * @param value
	 * @throws BusiException
	 */
	public static void setAttribute(String key, Object value) throws BusiException {
		/*if (logger.isDebugEnabled())
			logger.debug("set session[{}]=[{}]", key, value);
		getRequest().getSession().setAttribute(key, value);*/
		cache.put(key, value);
	}

	/**
	 * 删除session值
	 * @param key
	 * @throws BusiException
	 */
	public static void removeAttribute(String key) throws BusiException {
		if (logger.isDebugEnabled())
			logger.debug("remove session[{}]", key);
		getRequest().getSession().removeAttribute(key);
	}

	/**
	 * 清空session
	 * @param request 可为空
	 * @param prex 若有值，以该prex开头的key不删除
	 * @return 返回删除的条目数
	 * @throws BusiException
	 */
	public static int removeAllSession(HttpServletRequest request, String prex) throws BusiException {
		if (request == null)
			request = getRequest();
		HttpSession session = request.getSession();
		Enumeration<?> e = session.getAttributeNames();
		String key = null;
		int count = 0;
		while (e.hasMoreElements()) {
			key = (String) e.nextElement().toString();			
			if ("lasturl".equals(key))
				continue;
			if (prex != null && !key.startsWith(prex))
				continue;
			if (key.startsWith("NOTAUTOREMOVE_")) continue;
			
			if (logger.isDebugEnabled()) logger.debug("remove session[{}]",key);
			session.removeAttribute(key);
			count++;
		}
		return count;
	}

	/**
	 * 获取客户端ip地址
	 * @param request 可为空
	 * @return
	 * @throws BusiException
	 */
	public static String getClientIp(HttpServletRequest request) throws BusiException {
		if (request == null)
			request = getRequest();
		String ip = null;
		ip = request.getHeader(HTTP_JSFUND_CLIENTIP);
		if (ip == null || ip.trim().length() == 0) {
			ip = request.getRemoteAddr();
		}
		return ip;
	}

	/**
	 * 将http请求转化成map对象
	 * @param request 可为空
	 * @param charset 字符集
	 * @return
	 * @throws Exception
	 */
	public static Map<String, String> getRequestParameters(HttpServletRequest request, String charset)
			throws BusiException {
		if (request == null)
			request = getRequest();
		if (charset != null) {
			try {
				request.setCharacterEncoding(charset);
			} catch (UnsupportedEncodingException ue) {
				throw new BusiException(BusiException.ERR_SYSTEM, "不支持的字符集:" + charset);
			}
		}

		Map<String, String> map = new HashMap<String, String>();
		int count = 0;
		int total = 200;

		Map<?, ?> params = request.getParameterMap();
		Iterator<?> it = params.keySet().iterator();
		String key = null;
		String value = null;
		while (it.hasNext() && count < total) {
			count++;
			key = (String) it.next();
			if ("submit".equals(key)) continue;
			value = request.getParameter(key);
			map.put(key, value);
		}
		return map;
	}

	public static String getParameter(Map map, String key) throws BusiException {
		return (String) map.get(key);
	}

	public static Map<String,String> getRequestInfo(HttpServletRequest request)
			throws Exception {
		if (request == null)
			return null;
		Map<String,String> map = new HashMap<String,String>();
		int count = 0;
		int total = 200;
		Enumeration<String> e = request.getHeaderNames();
		String key = null;
		String value = null;
		while (e.hasMoreElements() && count < total) {
			count++;
			key = (String) e.nextElement();
			value = request.getHeader(key);
			map.put("HTTP_HEADER_" + key, value);
		}

		count = 0;

		Map<?,?> params = request.getParameterMap();
		Iterator<?> it = params.keySet().iterator();

		while (it.hasNext() && count < total) {
			count ++;
			key = (String) it.next();
			value = request.getParameter(key);
			map.put("HTTP_PARAMETER_" + key, value);
		}
		map.put("ipaddress", getClientIp(request));
		return map;
	}
}
